﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading;
using System.Windows.Forms;

namespace UHFReaderDemo
{
    public partial class frm_Main : Form
    {

        private frm_LockData myform;

        public frm_Main()
        {
  

            Control.CheckForIllegalCrossThreadCalls = false;
            InitializeComponent();
        }
        private bool getuid = false;
        private void checkUidList()
        {
            while (true)
            {
                Thread.Sleep(1000 * 1);
                try
                {
                    if (getuid && cmb_UII.Items.Count > 0)//先停止
                    {
                        Thread.Sleep(200);
                        btn_Stop_Click(null, null);
                        ShowInfo($"已读到标签{ cmb_UII.Items[0].ToString()}");
                    }
                    if (!getuid && cmb_UII.Items.Count > 0 && textBox2.Text.Length<2)//停止后，如没有读取则进行
                    {
                        Thread.Sleep(300);
                        btn_Read_Click(null, null);
                    }
                }
                catch (Exception ex)
                {
                    ShowInfo($"后台线程有异常"+ex.Message);
                }
            }

        }
        private void frm_Main_Load(object sender, EventArgs e)
        {
            Thread 标签结果 = new Thread(checkUidList);
            标签结果.IsBackground = true;
            标签结果.Start();
            UHFReader.TagDetected += new UHFReader.TagDetectedDel(UHFReader_TagDetected);
            UHFReader.ReturnTagRecord += new UHFReader.ReturnTagRecordDel(UHFReader_ReturnTagRecord);
            UHFReader.SendAndReceive += new UHFReader.SendAndReceiveDel(UHFReader_SendAndReceive);
            UHFReader.ReturnSelectRecord += new UHFReader.ReturnSelectRecordDel(UHFReader_ReturnSelectRecord);
            UHFReader.AdvancedInventoryComplete += new UHFReader.AdvancedInventoryCompleteDel(UHFReader_AdvancedInventoryComplete);
            myform = new frm_LockData();
            myform.send += new frm_LockData.SendCallback(myform_send);

            RefreshCom();
            cmb_BaudRate.SelectedIndex = 1;

            for (Byte i = 0; i < 16; i++)
            {
                cmb_InitQ.Items.Add(i);
            }
            cmb_InitQ.SelectedIndex = 3;
            cmb_Bank.SelectedIndex = 3;

            for (Int32 i = 10; i < 31; i++)
            {
                cmb_SetPower.Items.Add(i);
            }
            cmb_SetPower.SelectedIndex = 16;
            cmb_PowerModel.SelectedIndex = 1;

            ShowFrequencySetting();
        }

        void myform_send(string str)
        {
            txt_LockData.Text = str;
        }

        void UHFReader_SendAndReceive(string Direction, byte[] Frame)
        {
            AddFrame(Direction, Frame);
        }

        void UHFReader_AdvancedInventoryComplete(byte Command, byte Status, int TagNumber)
        {
            throw new NotImplementedException();
        }

        void UHFReader_ReturnSelectRecord(byte Command, byte Status, byte[] SelectRecord)
        {
            throw new NotImplementedException();
        }

        void UHFReader_ReturnTagRecord(byte Command, byte Status, byte[] TagRecord)
        {
            throw new NotImplementedException();
        }

        void UHFReader_TagDetected(byte Command, byte Status, byte[] TagUII)
        {
            String strTagUII = ByteArrayToString(TagUII);
            String strRow = String.Format("识别|{0}|1|1|{1}|{2}|0", strTagUII, (TagUII.Length / 2).ToString(), strTagUII);
            AddRow(strRow);
            AddUII(strTagUII);
            ShowInfo(String.Format("检测到标签:{0}！", strTagUII));
        }

        delegate void ShowInfoDel(String msg);
        private void ShowInfo(String msg)
        {
            if (lst_Info.InvokeRequired)
            {
                ShowInfoDel d = new ShowInfoDel(ShowInfo);
                lst_Info.Invoke(d, msg);
            }
            else
            {
                lst_Info.Items.Insert(0, String.Format("{0}:{1}", DateTime.Now.ToLongTimeString(), msg));
            }
        }

        delegate void AddFrameDel(String Direction, Byte[] Frame);
        private void AddFrame(String Direction, Byte[] Frame)
        {
            if (lst_Frame.InvokeRequired)
            {
                AddFrameDel d = new AddFrameDel(AddFrame);
                lst_Frame.Invoke(d, Direction, Frame);
            }
            else
            {
                lst_Frame.Items.Insert(0, String.Format("{0}:{1}:{2}", DateTime.Now.ToLongTimeString(), Direction, ByteArrayToStringWithBlank(Frame)));
            }
        }

        delegate void AddRowDel(String myDataRow);
        private void AddRow(String myDataRow)
        {
            if (grdv_Data.InvokeRequired)
            {
                AddRowDel d = new AddRowDel(AddRow);
                grdv_Data.Invoke(d, myDataRow);
            }
            else
            {
                String[] temp = myDataRow.Split('|');
                if (temp[0].Equals("识别"))
                {
                    try
                    {
                        for (Int32 i = 0; i < grdv_Data.Rows.Count; i++)
                        {
                            if (grdv_Data.Rows[i].Cells[1].Value != null && grdv_Data.Rows[i].Cells[1].Value.ToString().Equals(temp[1]))
                            { grdv_Data.Rows[i].Cells[2].Value = Convert.ToString(Int32.Parse(grdv_Data.Rows[i].Cells[2].Value.ToString()) + 1); return; }
                        }
                        grdv_Data.Rows.Add(temp[0], temp[1], 1, ((Bank)Byte.Parse(temp[2])).ToString(), temp[3], temp[4], temp[5], Byte.Parse(temp[6]).ToString("X2"));
                    }
                    catch
                    {
                        grdv_Data.Rows.Add(temp[0], temp[1], 1, ((Bank)Byte.Parse(temp[2])).ToString(), temp[3], temp[4], temp[5], Byte.Parse(temp[6]).ToString("X2"));
                    }
                }
                else
                {
                    grdv_Data.Rows.Add(temp[0], temp[1], 1, ((Bank)Byte.Parse(temp[2])).ToString(), temp[3], temp[4], temp[5], Byte.Parse(temp[6]).ToString("X2"));
                }
            }
        }

        delegate void AddUIIDel(String TagUII);
        private void AddUII(String TagUII)
        {
            if (cmb_UII.InvokeRequired)
            {
                AddUIIDel d = new AddUIIDel(AddUII);
                cmb_UII.Invoke(d, TagUII);
            }
            else
            {
                if (cmb_UII.Items.IndexOf(TagUII) < 0)
                {
                    cmb_UII.Items.Add(TagUII);
                }
                cmb_UII.SelectedIndex = 0;
            }
        }

        /// <summary>
        /// 将字节数组转换为十六进制的字符串
        /// </summary>
        /// <param name="array">字节数组</param>
        /// <returns>字符串</returns>
        private static String ByteArrayToString(Byte[] array, Int32 StartPos, Int32 Length)
        {
            StringBuilder sb = new StringBuilder();
            for (Int32 index = StartPos; index < StartPos + Length; index++)
            { sb.Append(array[index].ToString("X2")); }
            return sb.ToString();
        }
        private static String ByteArrayToString(Byte[] array)
        {
            return ByteArrayToString(array, 0, array.Length);
        }
        private static String ByteArrayToStringWithBlank(Byte[] array, Int32 StartPos, Int32 Length)
        {
            StringBuilder sb = new StringBuilder();
            for (Int32 index = StartPos; index < StartPos + Length; index++)
            {
                sb.Append(array[index].ToString("X2"));
                sb.Append(" ");
            }
            return sb.ToString();
        }
        private static String ByteArrayToStringWithBlank(Byte[] array)
        {
            return ByteArrayToStringWithBlank(array, 0, array.Length);
        }

        private void RefreshCom()
        {
            String[] ComList = System.IO.Ports.SerialPort.GetPortNames();
            cmb_SerialPort.Items.Clear();
            cmb_SerialPort.Text = "";
            if (ComList.Length > 0)
            {
                foreach (String com in ComList)
                {
                    cmb_SerialPort.Items.Add(com);
                }
                cmb_SerialPort.SelectedIndex = 0;
            }
        }

        /// <summary>
        /// 将十六进制的字符串转换为字节数组
        /// </summary>
        /// <param name="str">字符串</param>
        /// <returns>字节数组</returns>
        private static Byte[] StringToByteArray(String str)
        {
            Byte[] data = new Byte[str.Length / 2];
            for (Int32 i = 0; i < data.Length; i++)
            {
                data[i] = Convert.ToByte(str.Substring(i * 2, 2), 16);
            }
            return data;
        }

        private enum Bank
        { Rsv = 0x00, UII = 0x01, TID = 0x02, User = 0x03 }

        //private class MyDataRow
        //{
        //        public String State;
        //        public String TagUII;
        //        public Byte Bank;
        //        public Int32 Address;
        //        public Int32 Length;
        //        public String Data;
        //        public Byte ErrorCode;

        //        public MyDataRow(String state, String tagUII, Byte bank, Int32 address, Int32 length, String data, Byte errorCode)
        //        {
        //                State = state;
        //                TagUII = tagUII;
        //                Bank = bank;
        //                Address = address;
        //                Length = length;
        //                Data = data;
        //                ErrorCode = errorCode;
        //        }

        //        public override string ToString()
        //        {
        //                return base.ToString();
        //        }
        //}

        private void btn_Clear_Click(object sender, EventArgs e)
        {
            lst_Frame.Items.Clear();
            lst_Info.Items.Clear();
            grdv_Data.Rows.Clear();
        }

        private void btn_Refresh_Click(object sender, EventArgs e)
        {
            RefreshCom();
        }

        private void btn_Open_Click(object sender, EventArgs e)
        {
            if (UHFReader.IsOpen)
            {
                ShowInfo("串口已经打开！");
                return;
            }
            if (cmb_SerialPort.SelectedIndex < 0)
            {
                ShowInfo("请选择您要打开的串口！");
                return;
            }
            if (cmb_BaudRate.SelectedIndex < 0)
            {
                ShowInfo("请选择您要使用的波特率！");
                return;
            }
            if (UHFReader.OpenAndConnect(cmb_SerialPort.Text, int.Parse(cmb_BaudRate.SelectedItem.ToString())) == ErrorCode.AllDone)
            {
                ShowInfo(String.Format("串口{0}打开成功！", cmb_SerialPort.Text));
                txt_State.Text = String.Format("打开; {0}; {1}; ", cmb_SerialPort.Text, int.Parse(cmb_BaudRate.SelectedItem.ToString()));
            }
            else
            {
                ShowInfo(String.Format("串口{0}打开失败！", cmb_SerialPort.Text));
                txt_State.Text = String.Format("关闭");
            }
            Boolean PaStatus;
            ErrorCode ec = UHFReader.GetPaStatus(out PaStatus, chk_CRC.Checked);
            if (ec == ErrorCode.AllDone)
            {
                txt_State.Text += "已连接";
            }
            else
            { txt_State.Text += "未连接"; }
        }

        private void btn_Close_Click(object sender, EventArgs e)
        {
            if (!UHFReader.IsOpen)
            {
                ShowInfo("串口尚未打开！");
                txt_State.Text = String.Format("关闭");
                return;
            }
            if (UHFReader.CloseAndDisconnect() == ErrorCode.AllDone)
            { ShowInfo(String.Format("串口关闭成功！")); txt_State.Text = String.Format("关闭"); }
            else
            { ShowInfo(String.Format("串口关闭失败！")); }
        }

        private void btn_Inventory_Click(object sender, EventArgs e)
        {
            label40.Text = "";
            cmb_UII.Items.Clear();
            textBox2.Text = "";
            if (!UHFReader.IsOpen)
            {
                ShowInfo(String.Format("请先连接设备并打开串口！"));
                return;
            }
            getuid = true;
            ErrorCode ec;
            if (rb_StepInventory.Checked)
            {
                Byte[] TagUII;
                ec = UHFReader.InventorySingle(out TagUII, chk_CRC.Checked);
                if (ec == ErrorCode.AllDone)
                {
                    String strTagUII = ByteArrayToString(TagUII);
                    String strRow = String.Format("识别|{0}|1|1|{1}|{2}|0", strTagUII, (TagUII.Length / 2).ToString(), strTagUII);
                    AddRow(strRow);
                    AddUII(strTagUII);
                    ShowInfo(String.Format("单步识别命令执行成功，识别到标签:{0}！", ByteArrayToString(TagUII)));
                }
                else
                { ShowInfo(String.Format("单步识别命令执行失败，错误代码为:{0}！", ec.ToString())); }
                return;
            }

            Boolean AntiFlag = rb_AnticollInventory.Checked;
            if (AntiFlag && (cmb_InitQ.SelectedIndex < 0))
            {
                ShowInfo(String.Format("请选择初始Q值！"));
                cmb_InitQ.Focus();
                return;
            }
            ec = UHFReader.Inventory(AntiFlag, Byte.Parse(cmb_InitQ.SelectedItem.ToString()), chk_CRC.Checked);
            if (ec == ErrorCode.AllDone)
            {
                btn_Inventory.Enabled = false;
                btn_Inventory.Text = "识别中--";
                ShowInfo(String.Format("{0}识别命令执行成功！", AntiFlag ? "防碰撞" : "单标签"));
            }
            else
            {
                ShowInfo(String.Format("{0}识别命令执行失败，错误代码为:{1}！", AntiFlag ? "防碰撞" : "单标签", ec.ToString()));
            }
        }

        private void btn_Stop_Click(object sender, EventArgs e)
        {
            if (!UHFReader.IsOpen)
            {
                ShowInfo(String.Format("请先连接设备并打开串口！"));
                return;
            }
            ErrorCode ec;
            ec = UHFReader.StopInventory(chk_CRC.Checked);
            if (ec == ErrorCode.AllDone)
            {
                btn_Inventory.Enabled = true;
                btn_Inventory.Text = "标签识别";
                getuid = false;
                ShowInfo(String.Format("停止识别命令执行成功！"));
            }
            else
            {
                ShowInfo(String.Format("停止识别命令执行失败，错误代码为:{0}！", ec.ToString()));
            }
        }

        private void btn_Read_Click(object sender, EventArgs e)
        {
            //检查是否连接
            if (!UHFReader.IsOpen)
            {
                ShowInfo(String.Format("请先连接设备并打开串口！"));
                return;
            }
            //检查是否选择UII
            if ((!chk_UII.Checked) && (cmb_UII.SelectedIndex < 0))
            {
                ShowInfo("请选择您要读取的标签UII！");
                cmb_UII.Focus();
                return;
            }
            if (cmb_Bank.SelectedIndex < 0)
            {
                ShowInfo("请选择您要读取的存储体！");
                cmb_Bank.Focus();
                return;
            }
            Byte[] UII = StringToByteArray(cmb_UII.SelectedItem.ToString());
            Byte Bank = (Byte)cmb_Bank.SelectedIndex;
            Int32 Point;
            try { Point = Int32.Parse(txt_Ptr.Text); }
            catch
            {
                ShowInfo("请您填写正确的起始序号(十进制)！");
                txt_Ptr.SelectAll();
                txt_Ptr.Focus();
                return;
            }
            Byte Count;
            try { Count = Byte.Parse(txt_Count.Text); }
            catch
            {
                ShowInfo("请您填写正确的数量(十进制，0~255)！");
                txt_Count.SelectAll();
                txt_Count.Focus();
                return;
            }
            Byte[] Password = new Byte[4]; ;
            if (chk_Secured.Checked)
            {
                try
                {
                    Password = StringToByteArray(txt_AccessPwd.Text);
                    if (Password.Length != 4)
                    {
                        ShowInfo("请您填写正确的访问密钥(十六进制，长度为四个字节)！");
                        txt_AccessPwd.SelectAll();
                        txt_AccessPwd.Focus();
                        return;
                    }
                }
                catch
                {
                    ShowInfo("请您填写正确的访问密钥(十六进制，长度为四个字节)！");
                    txt_AccessPwd.SelectAll();
                    txt_AccessPwd.Focus();
                    return;
                }
            }
            ErrorCode ec;
            Byte[] Data;
            if (chk_UII.Checked)
            {
                ec = UHFReader.ReadDataSingle(Password, Bank, Point, Count, out UII, out Data, chk_CRC.Checked);
                if (ec == ErrorCode.AllDone)
                {
                    String strTagUII = ByteArrayToString(UII);
                    String strData = ByteArrayToString(Data);
                    textBox2.Text = HexStringToString(strData, Encoding.UTF8);
                    AddUII(strTagUII);
                    String strRow = String.Format("读取|{0}|{1}|{2}|{3}|{4}|{5}", strTagUII, Bank, Point, Count, strData, (Byte)ec);
                    AddRow(strRow);
                    ShowInfo(String.Format("读取数据命令执行成功，标签({0})返回数据0x{1}！", strTagUII, strData));
                }
                else
                {
                    String strTagUII = ByteArrayToString(UII);
                    String strData = ByteArrayToString(Data);
                    String strRow = String.Format("读取|{0}|{1}|{2}|{3}|{4}|{5}", strTagUII, Bank, Point, Count, strData, (Byte)ec);
                    AddRow(strRow);
                    ShowInfo(String.Format("读取数据命令执行失败，错误代码为:{0}！", ec.ToString()));
                }
            }
            else
            {
                ec = UHFReader.ReadData(Password, Bank, Point, Count, UII, out Data, chk_CRC.Checked);
                if (ec == ErrorCode.AllDone)
                {
                    String strTagUII = ByteArrayToString(UII);
                    String strData = ByteArrayToString(Data);
                    textBox2.Text = HexStringToString(strData, Encoding.UTF8);
                    if (textBox2.Text.Length < 2) textBox2.Text = "空标签";
                  
                    if (textBox2.Text.IndexOf(textBox1.Text)>=0)
                    {
                        label40.Text = "写入成功/数据一致";
                      //  ShowInfo(String.Format("写入成功，标签({0})返回数据{1}！", strTagUII, textBox2.Text));
                    }
                    String strRow = String.Format("读取|{0}|{1}|{2}|{3}|{4}|{5}", strTagUII, Bank, Point, Count, strData, (Byte)ec);
                    AddRow(strRow);
                   // ShowInfo(String.Format("读取数据命令执行成功，标签({0})返回数据0x{1}！", strTagUII, strData));
                }
                else
                {
                    textBox2.Text = "本标签异常无法读取："+ ec.ToString();
                    String strTagUII = ByteArrayToString(UII);
                    String strData = ByteArrayToString(Data);
                    String strRow = String.Format("读取|{0}|{1}|{2}|{3}|{4}|{5}", strTagUII, Bank, Point, Count, strData, (Byte)ec);
                    AddRow(strRow);
                    ShowInfo(String.Format("读取数据命令执行失败，错误代码为:{0}！", ec.ToString()));
                }
            }
        }

        private void btn_LockGen_Click(object sender, EventArgs e)
        {
            if (myform.IsDisposed)
            {
                myform = new frm_LockData();
                myform.send += new frm_LockData.SendCallback(myform_send);
            }
            myform.ShowDialog();
        }

        private void btn_Write_Click(object sender, EventArgs e)
        {
            label40.Text = "";
            //检查是否连接
            if (!UHFReader.IsOpen)
            {
                ShowInfo(String.Format("请先连接设备并打开串口！"));
                return;
            }
            //检查是否选择UII
            if ((!chk_UII.Checked) && (cmb_UII.SelectedIndex < 0))
            {
                ShowInfo("请选择您要读取的标签UII！");
                cmb_UII.Focus();
                return;
            }
            if (cmb_Bank.SelectedIndex < 0)
            {
                ShowInfo("请选择您要读取的存储体！");
                cmb_Bank.Focus();
                return;
            }
            if (textBox1.Text.Length < 2)
            {
                MessageBox.Show("内容长度要大于2");
                
                return;
            }
            Byte[] UII = StringToByteArray(cmb_UII.SelectedItem.ToString());
            Byte Bank = (Byte)cmb_Bank.SelectedIndex;
            Int32 Point;
            try { Point = Int32.Parse(txt_Ptr.Text); }
            catch
            {
                ShowInfo("请您填写正确的起始序号(十进制)！");
                txt_Ptr.SelectAll();
                txt_Ptr.Focus();
                return;
            }
            Byte Count;
            Count = Byte.Parse("1");
            Byte[] Password = new Byte[4]; ;
            if (chk_Secured.Checked)
            {
                try
                {
                    Password = StringToByteArray(txt_AccessPwd.Text);
                    if (Password.Length != 4)
                    {
                        ShowInfo("请您填写正确的访问密钥(十六进制，长度为四个字节)！");
                        txt_AccessPwd.SelectAll();
                        txt_AccessPwd.Focus();
                        return;
                    }
                }
                catch
                {
                    ShowInfo("请您填写正确的访问密钥(十六进制，长度为四个字节)！");
                    txt_AccessPwd.SelectAll();
                    txt_AccessPwd.Focus();
                    return;
                }
            }
            //Byte[] Data = new Byte[0];
            //try
            //{ Data = StringToByteArray(txt_DATA.Text.Trim()); }
            //catch
            //{
            //    ShowInfo("请您填写正确的数据(十六进制)！");
            //    txt_DATA.SelectAll();
            //    txt_DATA.Focus();
            //    return;
            //}
            //if (Data.Length != (Count * 2))
            //{
            //    ShowInfo(String.Format("您填写的数据长度有误，请填写{0}个字({1}Byte)的十六进制数据！", Count, Count * 2));
            //    txt_DATA.SelectAll();
            //    txt_DATA.Focus();
            //    return;
            //}
            ErrorCode ec;
            if (chk_UII.Checked)
            {
                //ec = UHFReader.WriteDataSingle(Password, Bank, Point, Count, out UII, Data, chk_CRC.Checked);
                //if (ec == ErrorCode.AllDone)
                //{
                //    String strTagUII = ByteArrayToString(UII);
                //    String strData = ByteArrayToString(Data);
                //    AddUII(strTagUII);
                //    String strRow = String.Format("写入|{0}|{1}|{2}|{3}|{4}|{5}", strTagUII, Bank, Point, Count, strData, (Byte)ec);
                //    AddRow(strRow);
                //    ShowInfo(String.Format("写入数据命令执行成功，往标签({0})写入数据0x{1}！", strTagUII, strData));
                //}
                //else
                //{
                //    String strTagUII = ByteArrayToString(UII);
                //    String strData = ByteArrayToString(Data);
                //    String strRow = String.Format("写入|{0}|{1}|{2}|{3}|{4}|{5}", strTagUII, Bank, Point, Count, strData, (Byte)ec);
                //    AddRow(strRow);
                //    ShowInfo(String.Format("写入数据命令执行失败，错误代码为:{0}！", ec.ToString()));
                //}
            }
            else
            {
                var writeinfo = StringToHexString(textBox1.Text+"#", Encoding.UTF8);
                while (writeinfo.Length % 4 != 0)
                {
                    writeinfo = writeinfo + "0";
                }
                if (writeinfo.Length / 4 > 29)
                {
                    ShowInfo("内容太长，无法写入");
                    return;
                }
                int lentall = writeinfo.Length;
                int indexnow = 0;
                int pointindex = 1;
                bool write = true;
                while (true)
                {
                    if (indexnow > lentall - 4) break;
                    Byte[] Data = new Byte[0];
                    try
                    {
                        var info = writeinfo.Substring(indexnow, 4);
                        Data = StringToByteArray(info);
                    }
                    catch
                    {
                        ShowInfo("请您填写正确的数据(十六进制)！");
                        txt_DATA.SelectAll();
                        txt_DATA.Focus();
                        write = false;
                        return;
                    }

                    ec = UHFReader.WriteData(Password, Bank, pointindex, Count, UII, Data, chk_CRC.Checked);
                    if (ec == ErrorCode.AllDone)
                    {
                        String strTagUII = ByteArrayToString(UII);
                        String strData = ByteArrayToString(Data);
                        String strRow = String.Format("写入|{0}|{1}|{2}|{3}|{4}|{5}", strTagUII, Bank, Point, Count, strData, (Byte)ec);
                        AddRow(strRow);
                        ShowInfo(String.Format("写入数据命令执行成功，往标签({0})写入数据0x{1}！", strTagUII, strData));
                    }
                    else
                    {

                        String strTagUII = ByteArrayToString(UII);
                        String strData = ByteArrayToString(Data);
                        String strRow = String.Format("写入|{0}|{1}|{2}|{3}|{4}|{5}", strTagUII, Bank, Point, Count, strData, (Byte)ec);
                        AddRow(strRow);
                        ShowInfo(String.Format("写入数据命令执行失败，错误代码为:{0}！", ec.ToString()));
                        write = false;
                        label40.Text = "写入失败";
                        break;
                    }
                    indexnow += 4;
                    pointindex++;
                }
                if (write)
                {
                    btn_Read_Click(null,null);
                }

            }
        }

        private void btn_Erase_Click(object sender, EventArgs e)
        {
            //检查是否连接
            if (!UHFReader.IsOpen)
            {
                ShowInfo(String.Format("请先连接设备并打开串口！"));
                return;
            }
            //检查是否选择UII
            if (cmb_UII.SelectedIndex < 0)
            {
                ShowInfo("请选择您要读取的标签UII！");
                cmb_UII.Focus();
                return;
            }
            if (cmb_Bank.SelectedIndex < 0)
            {
                ShowInfo("请选择您要读取的存储体！");
                cmb_Bank.Focus();
                return;
            }
            Byte[] UII = StringToByteArray(cmb_UII.SelectedItem.ToString());
            Byte Bank = (Byte)cmb_Bank.SelectedIndex;
            Int32 Point;
            try { Point = Int32.Parse(txt_Ptr.Text); }
            catch
            {
                ShowInfo("请您填写正确的起始序号(十进制)！");
                txt_Ptr.SelectAll();
                txt_Ptr.Focus();
                return;
            }
            Byte Count;
            try { Count = Byte.Parse(txt_Count.Text); }
            catch
            {
                ShowInfo("请您填写正确的数量(十进制，0~255)！");
                txt_Count.SelectAll();
                txt_Count.Focus();
                return;
            }
            Byte[] Password = new Byte[4]; ;
            if (chk_Secured.Checked)
            {
                try
                {
                    Password = StringToByteArray(txt_AccessPwd.Text);
                    if (Password.Length != 4)
                    {
                        ShowInfo("请您填写正确的访问密钥(十六进制，长度为四个字节)！");
                        txt_AccessPwd.SelectAll();
                        txt_AccessPwd.Focus();
                        return;
                    }
                }
                catch
                {
                    ShowInfo("请您填写正确的访问密钥(十六进制，长度为四个字节)！");
                    txt_AccessPwd.SelectAll();
                    txt_AccessPwd.Focus();
                    return;
                }
            }
            ErrorCode ec;
            ec = UHFReader.EraseData(Password, Bank, Point, Count, UII, chk_CRC.Checked);
            if (ec == ErrorCode.AllDone)
            {
                String strTagUII = ByteArrayToString(UII);
                String strData = "";
                String strRow = String.Format("擦除|{0}|{1}|{2}|{3}|{4}|{5}", strTagUII, Bank, Point, Count, strData, (Byte)ec);
                AddRow(strRow);
                ShowInfo(String.Format("擦除数据命令执行成功！"));
            }
            else
            {
                String strTagUII = ByteArrayToString(UII);
                String strData = "";
                String strRow = String.Format("擦除|{0}|{1}|{2}|{3}|{4}|{5}", strTagUII, Bank, Point, Count, strData, (Byte)ec);
                AddRow(strRow);
                ShowInfo(String.Format("擦除数据命令执行失败，错误代码为:{0}！", ec.ToString()));
            }

        }

        private void btn_SaveFrame_Click(object sender, EventArgs e)
        {
            SaveFileDialog sfd = new SaveFileDialog();
            sfd.FileName = "DataFrame";
            sfd.Filter = "*.txt|*.txt";
            sfd.RestoreDirectory = true;
            if (sfd.ShowDialog() == DialogResult.OK)
            {
                using (System.IO.StreamWriter sw = new System.IO.StreamWriter(sfd.FileName, false, System.Text.Encoding.Default))
                {
                    foreach (string str in lst_Frame.Items)
                    {
                        sw.WriteLine(str);
                    }
                }
                ShowInfo(String.Format("数据帧信息保存成功！文件名为:\r\n{0}", sfd.FileName));
            }
        }

        private void btn_SaveInfo_Click(object sender, EventArgs e)
        {
            SaveFileDialog sfd = new SaveFileDialog();
            sfd.FileName = "OperationInfo";
            sfd.Filter = "*.txt|*.txt";
            sfd.RestoreDirectory = true;
            if (sfd.ShowDialog() == DialogResult.OK)
            {
                using (System.IO.StreamWriter sw = new System.IO.StreamWriter(sfd.FileName, false, System.Text.Encoding.Default))
                {
                    foreach (string str in lst_Info.Items)
                    {
                        sw.WriteLine(str);
                    }
                }
                ShowInfo(String.Format("操作信息保存成功！文件名为:\r\n{0}", sfd.FileName));
            }
        }

        private void btn_Quit_Click(object sender, EventArgs e)
        {
            if (MessageBox.Show("您确认要退出吗？", "提示", MessageBoxButtons.YesNo) == DialogResult.No)
            { return; }
            if (UHFReader.IsOpen)
            { UHFReader.CloseAndDisconnect(); }
            this.Close();
            Application.Exit();
        }

        private void btn_LockMem_Click(object sender, EventArgs e)
        {
            //检查是否连接
            if (!UHFReader.IsOpen)
            {
                ShowInfo(String.Format("请先连接设备并打开串口！"));
                return;
            }
            if (MessageBox.Show("您将要执行的锁定操作是不可逆的！\r\n您确认要依据当前的锁定码执行数据锁定吗？", "警告", MessageBoxButtons.YesNo) != DialogResult.Yes)
            {
                return;
            }
            //检查是否选择UII
            if (cmb_UII.SelectedIndex < 0)
            {
                ShowInfo("请选择您要读取的标签UII！");
                cmb_UII.Focus();
                return;
            }
            Byte[] UII = StringToByteArray(cmb_UII.SelectedItem.ToString());
            Byte[] Password = new Byte[4]; ;
            if (chk_Secured.Checked)
            {
                try
                {
                    Password = StringToByteArray(txt_AccessPwd.Text);
                    if (Password.Length != 4)
                    {
                        ShowInfo("请您填写正确的访问密钥(十六进制，长度为四个字节)！");
                        txt_AccessPwd.SelectAll();
                        txt_AccessPwd.Focus();
                        return;
                    }
                }
                catch
                {
                    ShowInfo("请您填写正确的访问密钥(十六进制，长度为四个字节)！");
                    txt_AccessPwd.SelectAll();
                    txt_AccessPwd.Focus();
                    return;
                }
            }
            if (txt_LockData.Text.Trim().Length < 6)
            {
                ShowInfo("请点击锁定选项按钮生成锁定码！");
                txt_LockData.SelectAll();
                btn_LockGen.Focus();
                return;
            }
            Byte[] LockData = StringToByteArray(txt_LockData.Text.Trim());
            ErrorCode ec;
            ec = UHFReader.LockMemory(Password, LockData, UII, chk_CRC.Checked);
            if (ec == ErrorCode.AllDone)
            {
                String strTagUII = ByteArrayToString(UII);
                String strRow = String.Format("锁定|{0}|{1}|{2}|{3}|{4}|{5}", strTagUII, "", "", "", txt_LockData.Text.Trim(), (Byte)ec);
                AddRow(strRow);
                ShowInfo(String.Format("锁定命令执行成功！"));
            }
            else
            {
                String strTagUII = ByteArrayToString(UII);
                String strRow = String.Format("锁定|{0}|{1}|{2}|{3}|{4}|{5}", strTagUII, "", "", "", txt_LockData.Text.Trim(), (Byte)ec);
                AddRow(strRow);
                ShowInfo(String.Format("锁定命令执行失败，错误代码为:{0}！", ec.ToString()));
            }
        }

        private void btn_KillTag_Click(object sender, EventArgs e)
        {
            //检查是否连接
            if (!UHFReader.IsOpen)
            {
                ShowInfo(String.Format("请先连接设备并打开串口！"));
                return;
            }
            if (MessageBox.Show("您将要执行的锁定操作是不可逆的！\r\n您确认要销毁该标签吗？", "警告", MessageBoxButtons.YesNo) != DialogResult.Yes)
            {
                return;
            }
            //检查是否选择UII
            if (cmb_UII.SelectedIndex < 0)
            {
                ShowInfo("请选择您要读取的标签UII！");
                cmb_UII.Focus();
                return;
            }
            Byte[] UII = StringToByteArray(cmb_UII.SelectedItem.ToString());
            Byte[] Password = new Byte[4]; ;
            try
            {
                Password = StringToByteArray(txt_KillPwd.Text);
                if (Password.Length != 4)
                {
                    ShowInfo("请您填写正确的销毁密钥(十六进制，长度为四个字节)！");
                    txt_KillPwd.SelectAll();
                    txt_KillPwd.Focus();
                    return;
                }
            }
            catch
            {
                ShowInfo("请您填写正确的销毁密钥(十六进制，长度为四个字节)！");
                txt_KillPwd.SelectAll();
                txt_KillPwd.Focus();
                return;
            }
            ErrorCode ec;
            ec = UHFReader.KillTag(Password, UII, chk_CRC.Checked);
            if (ec == ErrorCode.AllDone)
            {
                String strTagUII = ByteArrayToString(UII);
                String strRow = String.Format("销毁|{0}|{1}|{2}|{3}|{4}|{5}", strTagUII, "", "", "", "", (Byte)ec);
                AddRow(strRow);
                ShowInfo(String.Format("销毁命令执行成功！"));
            }
            else
            {
                String strTagUII = ByteArrayToString(UII);
                String strRow = String.Format("销毁|{0}|{1}|{2}|{3}|{4}|{5}", strTagUII, "", "", "", "", (Byte)ec);
                AddRow(strRow);
                ShowInfo(String.Format("销毁命令执行失败，错误代码为:{0}！", ec.ToString()));
            }
        }

        private void tsb_EPCCommand_Click(object sender, EventArgs e)
        {
            pnl_EPC.Visible = true;
            pnl_PowerAndFrequency.Visible = false;
        }

        private void tsb_FrequencyAndPower_Click(object sender, EventArgs e)
        {
            pnl_EPC.Visible = false;
            pnl_PowerAndFrequency.Visible = true;
        }

        private void btn_SetPower_Click(object sender, EventArgs e)
        {
            //检查是否连接
            if (!UHFReader.IsOpen)
            {
                ShowInfo(String.Format("请先连接设备并打开串口！"));
                return;
            }
            if (cmb_SetPower.SelectedIndex < 0)
            {
                ShowInfo("请选择输出功率值！");
                cmb_SetPower.Focus();
                return;
            }
            if (cmb_PowerModel.SelectedIndex < 0)
            {
                ShowInfo("请选择功率控制方式！");
                cmb_PowerModel.Focus();
                return;
            }
            Byte Power = Byte.Parse(cmb_SetPower.SelectedItem.ToString());
            if (cmb_PowerModel.SelectedIndex == 1)
            { Power |= 0x80; }
            ErrorCode ec;
            ec = UHFReader.SetPower(Power, 0x03, chk_CRC.Checked);
            if (ec == ErrorCode.AllDone)
            {
                ShowInfo(String.Format("设置功率命令执行成功！"));
            }
            else
            {
                ShowInfo(String.Format("设置功率命令执行失败，错误代码为:{0}！", ec.ToString()));
            }
        }

        private void btn_GetPower_Click(object sender, EventArgs e)
        {
            //检查是否连接
            if (!UHFReader.IsOpen)
            {
                ShowInfo(String.Format("请先连接设备并打开串口！"));
                return;
            }
            ErrorCode ec;
            Byte Power;
            ec = UHFReader.GetPower(out Power, chk_CRC.Checked);
            if (ec == ErrorCode.AllDone)
            {
                txt_GetPower.Text = String.Format("{0};{1}dBm", ((Power & 0x80) == 0x80) ? "自动控制" : "手动控制", (Power & 0x7F));
                txt_Power.Text = String.Format("{0}dBm", (Power & 0x7F));
                ShowInfo(String.Format("读取功率命令执行成功！"));
            }
            else
            {
                ShowInfo(String.Format("读取功率命令执行失败，错误代码为:{0}！", ec.ToString()));
            }
        }

        private void cmb_FrequencyModel_SelectedIndexChanged(object sender, EventArgs e)
        {
            if (cmb_FrequencyModel.SelectedIndex != 4)
            {
                UHFReader.FrequencySetting.SetFrequncy((Byte)cmb_FrequencyModel.SelectedIndex);
                ShowFrequencySetting();
                EnableControl(false);
            }
            else
            {
                UHFReader.FrequencySetting.FREMODE = 0x04;
                ShowFrequencySetting();
                EnableControl(true);
            }
        }

        private void bar_BaseFrequency_Scroll(object sender, EventArgs e)
        {
            Double FrequencyBase;
            switch (cmb_FrequencyBase.SelectedIndex)
            {
                case 0:
                    FrequencyBase = ((Double)840 + 0.05 * bar_BaseFrequency.Value);
                    UHFReader.FrequencySetting.BF = (UInt16)(Convert.ToInt32(Math.Floor(FrequencyBase)) * 32 + Convert.ToInt32((FrequencyBase - Math.Floor(FrequencyBase)) / 0.05));
                    ShowFrequencySetting();
                    break;
                case 1:
                    FrequencyBase = ((Double)840 + 0.125 * bar_BaseFrequency.Value);
                    UHFReader.FrequencySetting.BF = (UInt16)(Convert.ToInt32(Math.Floor(FrequencyBase)) * 32 + Convert.ToInt32((FrequencyBase - Math.Floor(FrequencyBase)) / 0.125));
                    ShowFrequencySetting();
                    break;
            }
        }

        private void btn_GetFrequency_Click(object sender, EventArgs e)
        {
            //检查是否连接
            if (!UHFReader.IsOpen)
            {
                ShowInfo(String.Format("请先连接设备并打开串口！"));
                return;
            }
            ErrorCode ec;
            Byte[] Frequency;
            ec = UHFReader.GetFrequency(out Frequency, chk_CRC.Checked);
            if (ec == ErrorCode.AllDone)
            {
                if (Frequency[0] != 4)
                { UHFReader.FrequencySetting.SetFrequncy(Frequency[0]); }
                else
                { UHFReader.FrequencySetting.SetFrequncy(Frequency); }
                ShowFrequencySetting();
                ShowInfo(String.Format("读取频率命令执行成功！"));
            }
            else
            {
                ShowInfo(String.Format("读取频率命令执行失败，错误代码为:{0}！", ec.ToString()));
            }
        }

        private void btn_SetFrequency_Click(object sender, EventArgs e)
        {
            //检查是否连接
            if (!UHFReader.IsOpen)
            {
                ShowInfo(String.Format("请先连接设备并打开串口！"));
                return;
            }
            Byte[] Frequency = UHFReader.FrequencySetting.GetFrequncy();
            ErrorCode ec;
            ec = UHFReader.SetFrequency(Frequency, chk_CRC.Checked);
            if (ec == ErrorCode.AllDone)
            {
                ShowInfo(String.Format("设置频率命令执行成功！"));
            }
            else
            {
                ShowInfo(String.Format("设置频率命令执行失败，错误代码为:{0}！", ec.ToString()));
            }
        }

        private void EnableControl(Boolean Flag)
        {
            txt_FrequencyRange.Enabled = Flag;
            cmb_FrequencyBase.Enabled = Flag;
            txt_FrequencyBase.Enabled = Flag;
            txt_BaseFrequency.Enabled = Flag;
            bar_BaseFrequency.Enabled = Flag;
            txt_EndFrequency.Enabled = Flag;
            txt_ChannelNumber.Enabled = Flag;
            cmb_ChannSpc.Enabled = Flag;
            txt_ChannSpc.Enabled = Flag;
            cmb_FrequencyHop.Enabled = Flag;
        }

        private void cmb_FrequencyBase_SelectedIndexChanged(object sender, EventArgs e)
        {
            UHFReader.FrequencySetting.FREBASE = (Byte)cmb_FrequencyBase.SelectedIndex;
            switch (cmb_FrequencyBase.SelectedIndex)
            {
                case 0:
                    txt_FrequencyBase.Text = "50";
                    bar_BaseFrequency.Minimum = 0;
                    bar_BaseFrequency.Maximum = (int)((960 - 840) / 0.05);
                    bar_BaseFrequency.Value = 0;
                    cmb_ChannSpc.Items.Clear();
                    for (int i = 1; i < 17; i++)
                    { cmb_ChannSpc.Items.Add(i); }
                    cmb_ChannSpc.SelectedIndex = UHFReader.FrequencySetting.SPC - 1;
                    break;
                case 1:
                    txt_FrequencyBase.Text = "125";
                    bar_BaseFrequency.Minimum = 0;
                    bar_BaseFrequency.Maximum = (int)((960 - 840) / 0.05);
                    bar_BaseFrequency.Value = 0;
                    cmb_ChannSpc.Items.Clear();
                    for (int i = 1; i < 7; i++)
                    { cmb_ChannSpc.Items.Add(i); }
                    cmb_ChannSpc.SelectedIndex = UHFReader.FrequencySetting.SPC - 1;
                    break;
            }

        }

        private void cmb_ChannSpc_SelectedIndexChanged(object sender, EventArgs e)
        {
            switch (cmb_FrequencyBase.SelectedIndex)
            {
                case 0:
                    txt_ChannSpc.Text = ((Int32)((cmb_ChannSpc.SelectedIndex + 1) * 50)).ToString();
                    break;
                case 1:
                    txt_ChannSpc.Text = ((Int32)((cmb_ChannSpc.SelectedIndex + 1) * 125)).ToString();
                    break;
            }
            UHFReader.FrequencySetting.SPC = (Byte)(cmb_ChannSpc.SelectedIndex + 1);
            ShowFrequencySetting();
        }

        private void cmb_FrequencyHop_SelectedIndexChanged(object sender, EventArgs e)
        {
            UHFReader.FrequencySetting.FREHOP = (Byte)(cmb_FrequencyHop.SelectedIndex);
        }

        private void ShowFrequencySetting()
        {
            cmb_FrequencyModel.SelectedIndex = UHFReader.FrequencySetting.FREMODE;
            cmb_FrequencyBase.SelectedIndex = UHFReader.FrequencySetting.FREBASE;
            switch (UHFReader.FrequencySetting.FREBASE)
            {
                case 0:
                    bar_BaseFrequency.Minimum = 0;
                    bar_BaseFrequency.Maximum = (int)((960 - 840) / 0.05);
                    bar_BaseFrequency.Value = (Int32)(((UHFReader.FrequencySetting.BF & 0xFFE0) / 32 - 840) / 0.05) + (Byte)(UHFReader.FrequencySetting.BF & 0x001F);
                    break;
                case 1:
                    bar_BaseFrequency.Minimum = 0;
                    bar_BaseFrequency.Maximum = (int)((960 - 840) / 0.125);
                    bar_BaseFrequency.Value = (Int32)(((UHFReader.FrequencySetting.BF & 0xFFE0) / 32 - 840) / 0.125) + (Byte)(UHFReader.FrequencySetting.BF & 0x001F);
                    break;
            }
            txt_ChannelNumber.Text = UHFReader.FrequencySetting.CN.ToString();
            cmb_ChannSpc.SelectedIndex = UHFReader.FrequencySetting.SPC - 1;
            cmb_FrequencyHop.SelectedIndex = UHFReader.FrequencySetting.FREHOP;
            Double StartFrequency = 0;
            Double EndFrequency = 0;
            switch (UHFReader.FrequencySetting.FREBASE)
            {
                case 0:
                    StartFrequency = ((UHFReader.FrequencySetting.BF & 0xFFE0) / 32) + (UHFReader.FrequencySetting.BF & 0x001F) * 0.05;
                    EndFrequency = StartFrequency + (UHFReader.FrequencySetting.CN - 1) * (UHFReader.FrequencySetting.SPC * 0.05);
                    break;
                case 1:
                    StartFrequency = ((UHFReader.FrequencySetting.BF & 0xFFE0) / 32) + (UHFReader.FrequencySetting.BF & 0x001F) * 0.125;
                    EndFrequency = StartFrequency + (UHFReader.FrequencySetting.CN - 1) * (UHFReader.FrequencySetting.SPC * 0.125);
                    break;
            }
            txt_BaseFrequency.Text = StartFrequency.ToString("0.000");
            txt_EndFrequency.Text = EndFrequency.ToString("0.000");
            txt_FrequencyRange.Text = String.Format("{0} — {1}", txt_BaseFrequency.Text, txt_EndFrequency.Text);
        }

        private void txt_ChannelNumber_TextChanged(object sender, EventArgs e)
        {
            Byte CN = 0x01;
            try { CN = Byte.Parse(txt_ChannelNumber.Text.Trim()); }
            catch
            { ShowInfo("频道数不能大于255！"); }
            UHFReader.FrequencySetting.CN = CN;
            Double StartFrequency = 0;
            Double EndFrequency = 0;
            switch (UHFReader.FrequencySetting.FREBASE)
            {
                case 0:
                    StartFrequency = ((UHFReader.FrequencySetting.BF & 0xFFE0) / 32) + (UHFReader.FrequencySetting.BF & 0x001F) * 0.05;
                    EndFrequency = StartFrequency + (UHFReader.FrequencySetting.CN - 1) * (UHFReader.FrequencySetting.SPC * 0.05);
                    if ((EndFrequency - StartFrequency) > 12)
                    { UHFReader.FrequencySetting.CN = 0x01; ShowInfo("频道数太多，频率基数为0时不能让带宽大于12MHz！"); }
                    break;
                case 1:
                    StartFrequency = ((UHFReader.FrequencySetting.BF & 0xFFE0) / 32) + (UHFReader.FrequencySetting.BF & 0x001F) * 0.125;
                    EndFrequency = StartFrequency + (UHFReader.FrequencySetting.CN - 1) * (UHFReader.FrequencySetting.SPC * 0.125);
                    if ((EndFrequency - StartFrequency) > 32)
                    { UHFReader.FrequencySetting.CN = 0x01; ShowInfo("频道数太多，频率基数为1时不能让带宽大于32MHz！"); }
                    break;
            }
            ShowFrequencySetting();
        }



        /// 字符串转16进制
        /// </summary>
        /// <param name="str">
        /// <param name="encode">
        /// <returns></returns>
        public static string StringToHexString(string str, Encoding encode)
        {
            byte[] b = encode.GetBytes(str);
            StringBuilder result = new StringBuilder();
            for (int i = 0; i < b.Length; i++)
            {
                result.Append(Convert.ToString(b[i], 16));
            }
            return result.ToString();
        }
        /// <summary>
        /// 16进制转换成字符串
        /// </summary>
        /// <param name="hs">
        /// <param name="encode">
        /// <returns></returns>
        public static string HexStringToString(string hs, Encoding encode)
        {

            byte[] b = new byte[hs.Length / 2];
            for (int i = 0; i < hs.Length / 2; i++)
            {
                StringBuilder strTemp = new StringBuilder();

                strTemp.Append(hs.Substring(i * 2, 2));
                b[i] = Convert.ToByte(strTemp.ToString(), 16);
            }
            return encode.GetString(b);
        }


    }
}
